package com.bcxj.apipassenger.Service;

import com.auth0.jwt.JWT;
import com.bcxj.internalcommon.constant.CommonStatusEnum;
import com.bcxj.internalcommon.constant.TokenConstant;
import com.bcxj.internalcommon.dto.ResponseResult;
import com.bcxj.internalcommon.dto.TokenResult;
import com.bcxj.internalcommon.response.TokenResponse;
import com.bcxj.internalcommon.util.JwtUtils;
import com.bcxj.internalcommon.util.RedisPrefixUtils;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.stereotype.Service;

import java.util.concurrent.TimeUnit;

/**
 * ClassName: TokenService
 * Package: com.bcxj.apipassenger.Service
 * Description:
 *
 * @Author BCXJ
 * @Create 2024/10/1 21:13
 * @Version 1.0
 * @Since 1.0
 */
@Service
public class TokenService {

    @Autowired
    private StringRedisTemplate stringRedisTemplate;

    public ResponseResult refreshToken(TokenResponse tokenResponse) {
        // 对token进行解析
        String accessToken = tokenResponse.getAccessToken();
        String refreshToken = tokenResponse.getRefreshToken();
        TokenResult tokenResult = JwtUtils.parseToken(accessToken);
        TokenResult tokenResult1 = JwtUtils.parseToken(refreshToken);
        if (!tokenResult.equals(tokenResult1)) {
            return ResponseResult.fail(CommonStatusEnum.TOKEN_ERROR);
        }
        // 检验redis是否还存在refreshToken
        String redisRefreshToken = stringRedisTemplate.opsForValue().get(RedisPrefixUtils.generatorTokenKey(tokenResult.getPhone(), tokenResult.getIdentity(), TokenConstant.REFRESH_TOKEN));
        // 如果不存在redisrefreshToken，刷新责任不被允许
        if(StringUtils.isBlank(redisRefreshToken)){
            return ResponseResult.fail(CommonStatusEnum.TOKEN_ERROR);
        }
        // 如果refreshToken 与 redis的不一致，也不应该刷新
        if(!redisRefreshToken.equals(refreshToken)){
            return ResponseResult.fail(CommonStatusEnum.TOKEN_ERROR);
        }

        // 解析成功，颁发新的token
        String newAccessToken = JwtUtils.generatorToken(tokenResult.getPhone(), tokenResult.getIdentity(), TokenConstant.ACCESS_TOKEN);
        String newRefreshToken = JwtUtils.generatorToken(tokenResult.getPhone(), tokenResult.getIdentity(), TokenConstant.REFRESH_TOKEN);
        String newAccessTokenKey = RedisPrefixUtils.generatorTokenKey(tokenResult.getPhone(), tokenResult.getIdentity(), TokenConstant.ACCESS_TOKEN);
        String newRefreshTokenKey = RedisPrefixUtils.generatorTokenKey(tokenResult.getPhone(), tokenResult.getIdentity(), TokenConstant.REFRESH_TOKEN);

        // 将新的token存入redis
        stringRedisTemplate.opsForValue().set(newAccessTokenKey, newAccessToken, 30, TimeUnit.MINUTES);
        stringRedisTemplate.opsForValue().set(newRefreshTokenKey, newRefreshToken, 1, TimeUnit.DAYS);

        return ResponseResult.success(new TokenResponse(newAccessToken, newRefreshToken));
    }

}
